package com.globalwave.common.db;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.LinkedList;
import java.util.List;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import com.globalwave.common.ThreadContext;


public class StatementManager {

	protected Log log = LogFactory.getLog(this.getClass()) ;
	
	public static StatementManager getInstance() {
		ThreadContext tc = ThreadContext.getNotNull() ;
		StatementManager sm = (StatementManager)tc.get(ThreadContext.STATEMENT_MANAGER) ;
		
		if (sm == null) {
			sm = new StatementManager() ;
			tc.put(ThreadContext.STATEMENT_MANAGER, sm) ;
		}
		
		return sm ;
	}
	
	protected List<PreparedStatement> statementsToClose = new LinkedList<PreparedStatement>();

	protected PreparedStatement get(Connection conn, String sql) throws Exception{
		return get(conn, sql, false) ;
	}
	
	protected PreparedStatement get(Connection conn, String sql, boolean isScroll) throws Exception{

	    PreparedStatement ps =
	    	isScroll?
	    			conn.prepareStatement(sql, ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY)
	    			:conn.prepareStatement(sql);
	    
	    statementsToClose.add(ps) ;
	    
	    return ps ;
	}

	protected void closeAll() throws Exception {
		Exception exceptionWillThrow = null;
	    for (int i = statementsToClose.size() - 1 ; i >= 0 ; i --) {
	        PreparedStatement ps = statementsToClose.get(i) ;
	        if (ps == null) {
	            continue ;
	        }

            try {
                ps.close();
            } catch (SQLException e) {
            	log.error(e, e) ;
            	exceptionWillThrow = new Exception(e);
            }
	    }    
	    
	    if (exceptionWillThrow != null) {
	    	throw exceptionWillThrow ;
	    }
	} 

}
